import { LIST_KEY, store } from '@/utils/store/store'
import { IListItem } from '../interfaces'
import { keyBy, map } from 'lodash-es'

export interface IApiStore {
    // 根据parentId获取列表，没有传parentId时获取根节点的子项
    getList(parentId?: string): Promise<IListItem[]>
    // 添加 或 修改
    save(item: IListItem | IListItem[]): Promise<IListItem[]>
}

class ApiStore implements IApiStore {
    // 获取列表
    async getList(
        parentId?: string,
        type?: IListItem['type'],
    ): Promise<IListItem[]> {
        const list = await store.get(LIST_KEY)
        if (!list) {
            store.set(LIST_KEY, [])
            return []
        }
        if (!parentId) {
            return list.filter(
                (item) => !item.parentId && (type ? item.type === type : true),
            )
        }
        return list.filter(
            (item) =>
                item.parentId === parentId &&
                (type ? item.type === type : true),
        )
    }

    // 获取所有列表
    async getAllList(): Promise<IListItem[]> {
        const list = await store.get(LIST_KEY)
        if (!list) {
            return []
        }
        return list
    }

    // 获取某个列表项
    async getListItem(id?: string): Promise<IListItem | null> {
        if (!id) {
            return Promise.reject('id 为空')
        }
        const allList = (await store.get(LIST_KEY)) || []
        const index = allList.findIndex((i) => i.id === id)
        if (index === -1) {
            return Promise.resolve(null)
        }
        return Promise.resolve(allList[index])
    }

    // 添加 或 修改
    async save(it: IListItem | IListItem[]) {
        let items = !Array.isArray(it) ? [it] : it
        if (!items.length) {
            return Promise.reject('更新项为空')
        }
        const allList = (await store.get(LIST_KEY)) || []
        items.forEach((item) => {
            // 是否已经存在
            const index = allList.findIndex((i) => i.id === item.id)
            if (index !== -1) {
                allList[index] = item
            } else {
                allList.push(item)
            }
        })
        await store.set(LIST_KEY, allList)
        return Promise.resolve(items)
    }

    // 批量添加
    async saveBatch(items?: IListItem[]) {
        if (!items || items.length === 0) {
            return
        }
        const allList = (await store.get(LIST_KEY)) || []

        items.forEach((item) => {
            const index = allList.findIndex((i) => i.id === item.id)
            if (index !== -1) {
                allList[index] = item
            } else {
                allList.push(item)
            }
        })

        await store.set(LIST_KEY, allList)
        return
    }

    // 删除api
    async deleteApiItem(id?: string) {
        if (!id) {
            return Promise.reject('id 为空')
        }
        const allList = (await store.get(LIST_KEY)) || []
        const index = allList.findIndex((i) => i.id === id)
        if (index === -1) {
            return Promise.reject('未找到该数据')
        }
        if (allList[index].type !== 'api') {
            return Promise.reject('该节点不是API节点')
        }
        allList.splice(index, 1)
        await store.set(LIST_KEY, allList)
        return
    }

    // 删除分组 及 分组下的所有API
    async deleteGroup(id?: string) {
        if (!id) {
            return Promise.reject('id 为空')
        }
        const allList = (await store.get(LIST_KEY)) || []
        const index = allList.findIndex((i) => i.id === id)
        if (index === -1) {
            return Promise.reject('未找到该数据')
        }
        if (allList[index].type !== 'group') {
            return Promise.reject('该节点不是分组节点')
        }

        // 收集所有需要删除的id（包括自身和所有子孙）
        const idsToDelete = new Set<string>([id])

        // 递归查找所有子孙节点
        const findChildren = (parentId: string) => {
            const children = allList.filter((item) => {
                return item.parentId === parentId
            })
            children.forEach((child) => {
                idsToDelete.add(child.id)
                if (child.type !== 'group') {
                    return
                }
                findChildren(child.id) // 递归查找子节点的子节点
            })
        }

        findChildren(id)

        // 过滤掉所有需要删除的节点
        const newList = allList.filter((item) => !idsToDelete.has(item.id))
        await store.set(LIST_KEY, newList)

        return
    }

    // 移动 item 到指定位置
    async moveItem(targetId: string, referenceId: string) {
        if (!targetId || !referenceId) {
            return Promise.reject('targetId 或 referenceId 为空')
        }
        
        if (targetId === referenceId) {
            return Promise.resolve() // 相同位置，无需移动
        }

        const allList = (await store.get(LIST_KEY)) || []
        
        // 找到目标 item 和参考 item
        const targetIndex = allList.findIndex((i) => i.id === targetId)
        const referenceIndex = allList.findIndex((i) => i.id === referenceId)
        
        if (targetIndex === -1 || referenceIndex === -1) {
            return Promise.reject('未找到目标或参考项')
        }
        
        const targetItem = allList[targetIndex]
        const referenceItem = allList[referenceIndex]
        
        // 标准化 parentId（undefined 和 "" 都视为根级别）
        const normalizeParentId = (parentId?: string) => parentId || undefined
        
        // 确保在同一层级（同一个 parentId）
        if (normalizeParentId(targetItem.parentId) !== normalizeParentId(referenceItem.parentId)) {
            return Promise.reject('不能在不同层级之间移动')
        }
        
        // 判断拖拽方向
        const isMovingRight = targetIndex < referenceIndex
        
        // 移除 targetItem
        allList.splice(targetIndex, 1)
        
        // 重新找到 referenceItem 的位置（因为删除后索引可能变化）
        let newReferenceIndex = allList.findIndex((i) => i.id === referenceId)
        
        // 如果是从左往右拖，插入到 referenceItem 之后
        // 如果是从右往左拖，插入到 referenceItem 的位置（之前）
        if (isMovingRight) {
            newReferenceIndex += 1
        }
        
        allList.splice(newReferenceIndex, 0, targetItem)
        
        await store.set(LIST_KEY, allList)
        return Promise.resolve()
    }
}

export const apiStore = new ApiStore()
